#include <iostream>
#ifndef Nodeok
#define Nodeok
//using namespace std;
namespace MyStructDate{
template <class TYPE>
class Node{
    TYPE info;
    public:
    inline void setInfo(TYPE input){info=input;}
    Node<TYPE> *next;
    //Node<TYPE> *last;
    TYPE getinfo(){return info;}
    //friend ostream & operator<<(ostream & os,Node<TYPE> *&nod);
    //void operator +(Node<TYPE> *&nex);
    //void operator -(/*Node<TYPE> *&las*/int varr);
    Node();
    Node(TYPE infoi);
    void deleteNode(Node<TYPE> *&start);//delete this Node
    void addHead(Node<TYPE> *&start);//put this Node in the starts
    void addTail(Node<TYPE> *&end);//put this Node in the end
};
template<class TYPE>
Node<TYPE>::Node(){
    TYPE infoi;
    info = infoi;
    next = NULL;
    //last = NULL;
}
template<class TYPE>
Node<TYPE>::Node(TYPE infoi){
    info = infoi;
    next = NULL;
    //last = NULL;
}
template<class TYPE>
void Node<TYPE>::deleteNode(Node<TYPE> *& start){
     //if(last!=NULL)
// last->next = next;
	bool found = false;
	Node<TYPE> *ptr = start;
	if(ptr ==NULL){return;}
	if (ptr->info == info){
		start =ptr->next;
        delete ptr;
        return;
        //found =true;
		//return true;
	}
	while(ptr->next != NULL && !found){
	if(ptr->next->info == info){
		Node<TYPE> *ptr2;
        ptr2 = ptr->next;
        ptr->next = ptr->next->next;
        found = true;
		delete ptr2;
	}
    if(!found){
        ptr = ptr->next;
    }
    }
	//next->last = last;
    //delete this; //delete himself
}
template<class TYPE>
void Node<TYPE>::addHead(Node<TYPE> *& start){
   /* if (start->last != NULL){
        start->last->next = this;
        last = start->last;
    }*/
    next = start;
    start = this;
}
template<class TYPE>
void Node<TYPE>::addTail(Node<TYPE> *&end){
    if(end==NULL){
	    end =this;
	    return;
    }
	Node<TYPE> *ptr;
    ptr = end;
    while(ptr->next != NULL){
        ptr = ptr->next;
    }
    ptr->next =this;
    //last = ptr;
}
//template<class TYPE>
//void operator+(Node<TYPE> *&thiss,Node<TYPE> *&nex){
   // nex->addTail(thiss);
//}
//template<class TYPE>
//void Node<TYPE>::operator-(/*Node<TYPE> *&las*/int varr){
   // Node<TYPE> *ptr;
    //ptr = this;
    //while(ptr->next != NULL){
    //    ptr = this->next;
    //}
//     //for(int i =0;i<varr;i++){
//         ptr =ptr->last;
//         delete ptr->next;
//     }
// }
template<class TYPE>
std::ostream & operator<<(std::ostream & os,Node<TYPE> *&nod){
    Node<TYPE> *ptr;
    ptr = nod;
    if(ptr == NULL){
        os<<"nil\n";
        return os;
    }
    while(ptr!=NULL){
        os<<ptr->getinfo()<<"\n";
        ptr = ptr->next;
    }
    return os;
}

template<class TYPE>
void EmptyTable(Node<TYPE> *&start){
	//Node<TYPE> *ptr=start,*ptr2;
	if(start ==NULL){return;}
	while(start!=NULL){
		start->deleteNode(start);
	}
	/*while(ptr->next !=NULL){
		ptr2=ptr;
		ptr=ptr->next;
		ptr2
	}*/
}
template<class TYPE>
void deepCopy(Node<TYPE> *& target,Node<TYPE> * start){
	if(target !=NULL)
	{EmptyTable(target);}
	Node<TYPE> *ptr=start,*ptr2=NULL;
	if(start ==NULL){return;}
	while(ptr->next!=NULL){
		if(target ==NULL){
		target=new Node<TYPE>(ptr->getinfo());
		ptr2 =target;continue;
		}else{
			ptr =ptr->next;

			ptr2->next =new Node<TYPE>(ptr->getinfo());
			ptr2 =ptr2->next;
			//ptr=ptr->next;
		}
	}
}
template<class TYPE>
using _List = Node<TYPE> * ;
/*/*
//Node<int> Nod1(22),Nod2(23);
 /*Node<int> *Node1 =new Node<int>(22);
 Node<int> *Node2 =new Node<int>(23);

 int main(){ */
   //  Node<int> *start,*target=NULL,/*Node33=*Node2,*///*Node3=new Node<int>(24);
     //start = Node2;
     //Node1->addHead(start);
     //Node3->addTail(start);
/**///     /*//Node1+Node2;
//     //ptr =start;*/
/*	cout<<start;
	deepCopy(target,start);
	
     Node2->deleteNode(start);
    // EmptyTable(start);
//     /*///Node3->deleteNode();*/
   /*  cout<<start;
     cout<<target;*/
//     /*// while(ptr!=NULL){
//     //     cout<<ptr->getinfo()<<"\n";
//     //     ptr = ptr->next;
//     // }*/
 //}
}
#endif
